<?php

declare(strict_types=1);

namespace App\Activity\Controller;

use App\Activity\Request\SeckillActivityRequest;
use App\Activity\Service\ActivityService;
use App\Common\Constants\ErrorCode;
use App\Common\Controller\AbstractController;
use App\Common\Middleware\JwtAuthMiddleware;
use App\Common\Middleware\PermissionMiddleware;
use Carbon\Carbon;
use Hyperf\Di\Annotation\Inject;
use Hyperf\HttpServer\Annotation\Controller;
use Hyperf\HttpServer\Annotation\DeleteMapping;
use Hyperf\HttpServer\Annotation\Middleware;
use Hyperf\HttpServer\Annotation\Middlewares;
use Hyperf\HttpServer\Annotation\PutMapping;
use Hyperf\HttpServer\Annotation\RequestMapping;
use Hyperf\HttpServer\Contract\RequestInterface;

/**
 * @Controller
 * Class SeckillActivityController
 * @package App\Activity\Controller
 */
class SeckillActivityController extends AbstractController
{
    /**
     * @Inject()
     * @var ActivityService
     */
    private $actService;

    const SECKILLACTIVITY = 4;

    /**
     * 获取秒杀活动列表
     * @RequestMapping(path="/v1/activity/seckill", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param RequestInterface $request
     *
     * @return array
     */
    public function index(RequestInterface $request)
    {
        $params = $request->all();
        $perPage = !empty($params['perpage']) ? $params['perpage'] : 15;
        $field = ['activityID', 'title', 'activity_prams', 'begin_date', 'status', 'create_at', 'shop_ids'];
        $res = $this->actService->getList($params, (int)$perPage, self::SECKILLACTIVITY, $field);
        if (!$res['code']) {
            return $this->success($res['data']->items(), '获取成功', $res['data']->total());
        } else {
            return $this->failed($res['code']);
        }
    }

    /**
     * 获取秒杀活动详情
     * @RequestMapping(path="/v1/activity/{id:\d+}/seckill", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param int $id
     *
     * @return array
     */
    public function info(int $id, RequestInterface $request)
    {
        $params = $request->all();
        $field = ['activityID', 'title', 'begin_date', 'activity_prams', 'shop_ids','status'];
        $res = $this->actService->getInfoById($id, self::SECKILLACTIVITY, $field, $params);
        if (!$res['code']) {
            return $this->success($res['data'], '获取成功');
        } else {
            return $this->failed($res['code']);
        }
    }

    /**
     * 添加秒杀活动
     * @RequestMapping(path="/v1/activity/seckill", methods="post")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param SeckillActivityRequest $request
     *
     * @return array
     */
    public function store(SeckillActivityRequest $request)
    {
        $params = $request->validated();
        $res = $this->actService->add($params, self::SECKILLACTIVITY);
        if (!$res['code']) {
            return $this->success($res['data'], '操作成功');
        } else {
            if(!empty($res['msg'])){
                return $this->failed($res['code'], $res['msg']);
            }
            return $this->failed($res['code']);
        }
    }

    /**
     * 编辑秒杀活动
     * @PutMapping(path="/v1/activity/{id:\d+}/seckill", methods="put")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param SeckillActivityRequest $request
     *
     * @return array
     */
    public function update(int $id, SeckillActivityRequest $request)
    {
        $params = $request->validated();
        $params['id'] = $id;
        $res = $this->actService->update($params, self::SECKILLACTIVITY);
        if (!$res['code']) {
            return $this->success($res['data'], '操作成功');
        } else {
            if(!empty($res['msg'])){
                return $this->failed($res['code'], $res['msg']);
            }
            return $this->failed($res['code']);
        }
    }

    /**
     * 小程序次日达秒杀模块
     * @RequestMapping(path="/v1/api/seckill", methods="get")
     * @return array
     * @author liule
     */
    public function miniAppHomeSeckill(){
        $shopId = $this->request->input('shop_id');
        $mid = $this->request->input('mid');
        $type = $this->request->input('type');
        if (empty($shopId)) return $this->failed(ErrorCode::SYSTEM_INVALID, '店铺信息错误');
        if (!is_numeric($mid)) $mid = 0;
        switch ($type){
            case 'current':
                $res = $this->actService->getMiniAppHomeSecKill((string)$shopId, (int)$mid);
                break;
            case 'all':
                $res = $this->actService->getMiniAppSecKillAll((string)$shopId, (int)$mid);
                break;
            default:
        }

        return $this->success($res['data'], $res['msg']);
    }

    /**
     * 禁用/启用
     * @PutMapping(path="/v1/activity/status/{id:\d+}/seckill", methods="put")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param int $id
     * @return array
     */
    public function editStatus(int $id)
    {
        $res = $this->actService->seckillStatus((int)$id);
        if (!$res['code']) {
            return $this->success($res['data'], '操作成功');
        } else {
            return $this->failed($res['code']);
        }
    }

    /**
     * 秒杀活动新增门店
     * @PutMapping(path="/v1/activity/shop/{id:\d+}/seckill", methods="put")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param int $id
     * @return array
     */
    public function addShop(int $id, RequestInterface $request)
    {
        $shopIds = $request->input('shop_ids');
        if(!$id || !$shopIds){
            return $this->failed(ErrorCode::SYSTEM_INVALID);
        }
        $res = $this->actService->addShop((int)$id,$shopIds);
        if (!$res['code']) {
            return $this->success($res['data'], '操作成功');
        } else {
            return $this->failed($res['code']);
        }
    }

    /**
     * 删除秒杀活动
     * @DeleteMapping(path="/v1/activity/{id:\d+}/seckill", methods="delete")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param int $id
     * @return array
     */
    public function delete(int $id)
    {
        $res = $this->actService->delete($id, self::SECKILLACTIVITY);
        if (!$res['code']) {
            return $this->success($res['data'], '操作成功');
        } else {
            return $this->failed($res['code']);
        }
    }

    /**
     * 发送秒杀提醒
     *
     * @RequestMapping(path="/v1/activity/seckill/remind", methods="post")
     * @Middleware(JwtAuthMiddleware::class)
     *
     * User: mengchenchen
     * Created_at: 2020/12/29 0029 15:48
     * Updated_at: 2020/12/29 0029 15:48
     *
     * @param RequestInterface $request
     * @return array
     */
    public function setSpikeReminder(RequestInterface $request)
    {
        $mid = $request->input('mid', 0);
        if (!intval($mid)) {
            return $this->failed(ErrorCode::PARAMS_INVALID);
        }
        $activity_goods_id = $request->input('activity_goods_id', null);
        $preempt_time = $request->input('preempt_time', null);
        if ($activity_goods_id) {
            $result = $this->actService->setSpikeGoodsReminder($mid, $activity_goods_id, $preempt_time);
        } else {
            $shop_id = $request->input('shop_id', 0);
            $result = $this->actService->setSpikeClosestActivityReminder($shop_id, $mid);
        }
        if (!$result['code']) {
            return $this->success([], '操作成功');
        } else {
            return $this->failed($result['code'], $result['msg']);
        }
    }

    /**
     * 销售数据统计
     * @RequestMapping(path="/v1/activity/salesStatistics", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param RequestInterface $request
     * @return array
     *
     * 说明：包含秒杀商品的订单，都算是秒杀订单。混合订单中，秒杀商品退完了，依旧属于秒杀订单。
     * 销售额，销售量等统计，只考虑秒杀订单的数据，不需要考虑混合订单退款情况。
     */
    public function salesStatistics()
    {
        $today = Carbon::today()->toDateString();  // 2020-12-16
        $yesterday = Carbon::yesterday()->toDateString(); // 2020-12-15
        $sevenDayAgo = Carbon::parse('-7 days')->toDateString(); // 2020-12-09

        $totalSales = $this->actService->totalSales();  // 销售总额
        $todaySales = $this->actService->totalSales($today);    // 今日销售额
        $yesterdaySales = $this->actService->totalSales($yesterday);    // 昨日销售额
        $sevenDayAgoSales = $this->actService->totalSales($sevenDayAgo);    // 七天前的销售额

        $cumulativeSalesDays = $this->actService->cumulativeSalesDays(); // 累计销售天数

        $salesVolume = $this->actService->seckillSalesVolume(); // 销售量，不含退货数量（只要是秒杀订单的商品，都算秒杀销售量）

        $totalReturnAmount = $this->actService->getSeckillRefundAmount(); // 退款总金额
        $todayReturnAmount = $this->actService->getSeckillRefundAmount($today); // 今天退款金额
        $yesterdayReturnAmount = $this->actService->getSeckillRefundAmount($yesterday); // 昨天退款金额
        $sevenDayAgoReturnAmount = $this->actService->getSeckillRefundAmount($sevenDayAgo); // 七天前的退款金额

        $orderNum = $this->actService->seckillOrderNum();   // 秒杀订单数总量

        // 秒杀销售总额
        $res[0]['total_sales'] = $totalSales;

        // 销售额周同比---（本期数－同期数）÷同期数×100%
        if($sevenDayAgoSales == 0){
            $res[0]['total_sales_weekly_comparison'] = '0%';
        }else{
            $res[0]['total_sales_weekly_comparison'] = round(bcdiv((string)bcsub((string)$todaySales, (string)$sevenDayAgoSales, 2), (string)$sevenDayAgoSales, 2)).'%';
        }

        // 销售额日环比---（今日销售额-昨日销售额）÷昨日销售额×100%
        if($yesterdaySales == 0){
            $res[0]['total_sales_today_than_yesterday'] = '0%';
        }else{
            $res[0]['total_sales_today_than_yesterday'] = round(bcdiv((string)bcsub((string)$todaySales, (string)$yesterdaySales, 2), (string)$yesterdaySales, 2)).'%';
        }

        // 日均销售额---总销售额÷累计销售天数， 额外注意：此处为累计销售天数，若其中中断N天未做秒杀活动，那么累计销售天数不包含N
        $res[0]['average_daily_sales_money'] = bcdiv((string)$res[0]['total_sales'], (string)$cumulativeSalesDays,2);

        // 销售量--秒杀商品支付数量（不含退货数量）
        $res[0]['sales_volume'] = $salesVolume;
        // 日均销售量---销售量÷累计销售天数
        $res[0]['average_daily_sales_count'] = round(bcdiv((string)$salesVolume, (string)$cumulativeSalesDays,2));

        // 秒杀订单数
        $res[0]['order_num'] = $orderNum;
        // 日均订单数：订单数÷累计销售天数
        $res[0]['average_daily_order_num'] = round(bcdiv((string)$orderNum, (string)$cumulativeSalesDays, 2));

        // 秒杀退款金额---秒杀活动产生的订单的退货金额合计
        $res[0]['return_amount'] = $totalReturnAmount;
        //退款金额周同比---（本期数－同期数）÷同期数×100%
        if($sevenDayAgoReturnAmount == 0){
            $res[0]['return_amount_weekly_comparison'] = '0%';
        }else{
            $res[0]['return_amount_weekly_comparison'] = round(bcdiv((string)bcsub((string)$todayReturnAmount, (string)$sevenDayAgoReturnAmount, 2), $sevenDayAgoReturnAmount, 2)).'%';
        }
        //退款金额日环比---（今日退货金额-昨日退货金额）÷昨日退货金额×100%
        if($yesterdayReturnAmount == 0){
            $res[0]['return_amount_today_than_yesterday'] = '0%';
        }else{
            $res[0]['return_amount_today_than_yesterday'] = round(bcdiv((string)bcsub((string)$todayReturnAmount, (string)$yesterdayReturnAmount, 2), (string)$yesterdayReturnAmount, 2)).'%';
        }

        return $this->success($res, '操作成功');
    }

    /**
     * 销售额趋势柱状图
     * @RequestMapping(path="/v1/activity/salesTrend", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param RequestInterface $request
     * @return array
     */
    public function salesTrend(RequestInterface $request)
    {
        $params = $request->all();
        $res = $this->actService->salesTrend($params);
        if ($res['code']) {
            return $this->failed($res['code']);
        } else {
            return $this->success($res['data'], '操作成功');
        }
    }
    /**
     * 门店销售额排名
     * @RequestMapping(path="/v1/activity/seckillStoreSalesRanking", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @param RequestInterface $request
     * @return array
     */
    public function storeSalesRanking(RequestInterface $request)
    {
        $params = $request->all();
        $res = $this->actService->seckillStoreSalesRanking($params);
        if ($res['code']) {
            return $this->failed($res['code']);
        } else {
            return $this->success($res['data'], '操作成功');
        }
    }

    /**
     * 活动数据分析列表
     * @RequestMapping(path="/v1/activity/activityDataAnalysis", methods="get")
     * @Middlewares({
     *     @Middleware(JwtAuthMiddleware::class),
     *     @Middleware(PermissionMiddleware::class)
     * })
     * @return array
     */
    public function activityDataAnalysis(RequestInterface $request)
    {
        $params = $request->all();
        $res = $this->actService->activityDataAnalysis($params);
        if ($res['code']) {
            return $this->failed($res['code']);
        } else {
            return $this->success($res['data'], '操作成功');
        }
    }

}

